package com.tykboot.gem;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.sql.*;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 代码生成器
 *
 * @author LiuYu
 */
public class GenTool {
    private static Logger logger = LoggerFactory.getLogger(GenTool.class);

    public static String entityPackageOutPath = "com.tykboot.entity";//指定实体生成所在包的路径
    public static String daoPackageOutPath = "com.tykboot.dao";//指定Dao所在包的路径
    public static String svcPackageOutPath = "com.tykboot.service";//指定service接口所在包的路径
    public static String svcImplPackageOutPath = "com.tykboot.service.impl";//指定service实现所在包的路径
    public static String webPackageOutPath = "com.tykboot.controller";//指定Controller实现所在包的路径
    public static String authorName = "LiuYu";//作者名字

    //数据库连接
    private static final String DRIVER = "com.mysql.cj.jdbc.Driver";
    private static final String URL = "jdbc:mysql://139.199.196.17:3306/tyk?characterEncoding=utf8";
    private static final String NAME = "gamma";
    private static final String PASS = "LiuYu199065!";
    private static final String TABLE_SCHEMA = "tyk";
    private static final String COLUMN_SQL = "SELECT table_name AS tableName, column_name AS columnName, data_type AS dataType, " +
            "column_comment AS columnComment, column_key AS columnKey, extra AS extra FROM information_schema.columns " +
            "WHERE table_schema ='" + TABLE_SCHEMA + "' AND table_name = '%s' ORDER BY table_name ASC, ordinal_position ASC;";
    private static final String TABLE_SQL = "SELECT TABLE_NAME,TABLE_COMMENT FROM information_schema.TABLES " +
            "WHERE TABLE_SCHEMA='" + TABLE_SCHEMA + "' AND TABLE_TYPE='BASE TABLE' AND TABLE_NAME LIKE '%s';";

    public static void main(String[] args) throws Exception {
//        entityPackageOutPath = "com.tykboot.entity.sys";
//        daoPackageOutPath = "com.tykboot.dao.sys";
//        svcPackageOutPath = "com.tykboot.service.sys";
//        svcImplPackageOutPath = "com.tykboot.service.sys.impl";
//        webPackageOutPath = "com.tykboot.controller.sys";
        gen("tb_t%", false, false, false, true, "");
    }

    /**
     * 构造函数
     */
    public static void gen(String tbName, boolean isGenEntity, boolean isGenDao, boolean isGenService,
                           boolean isGenWeb, String prefix) {
        //创建连接
        Connection con = null;
        //查要生成实体类的表
        String tableSql = String.format(TABLE_SQL, tbName);
        logger.info("查询表结构：{}", tableSql);
        PreparedStatement pStemt = null;
        try {
            try {
                Class.forName(DRIVER);
            } catch (ClassNotFoundException e1) {
                e1.printStackTrace();
            }
            con = DriverManager.getConnection(URL, NAME, PASS);
            pStemt = con.prepareStatement(tableSql);
            ResultSet tablesResultSet = pStemt.executeQuery();
            ResultSet columnResultSet;
            Map<String, Object> columnMap = new HashMap<>();
            List<ColumnInfo> columnInfos;
            JSONObject tableJsonObject;
            while (tablesResultSet.next()) {
                String tName = tablesResultSet.getString(1);
                String tableComment = tablesResultSet.getString(2);
                String entitySql = String.format(COLUMN_SQL, tName);
                logger.info("查询表字段：{}, {}", tableComment, entitySql);
                pStemt = con.prepareStatement(entitySql);
                columnResultSet = pStemt.executeQuery();
                tableJsonObject = new JSONObject();
                columnInfos = new ArrayList<>();
                while (columnResultSet.next()) {
                    columnInfos.add(new ColumnInfo(columnResultSet.getString(2), columnResultSet.getString(3), columnResultSet.getString(4), columnResultSet.getString(5), columnResultSet.getString(6)));
                }
                tableJsonObject.put("columnInfos", columnInfos);
                tableJsonObject.put("tableComment", tableComment);
                columnMap.put(tName, tableJsonObject);
            }

            for (Map.Entry<String, Object> map : columnMap.entrySet()) {
                JSONObject objects = JSON.parseObject(JSON.toJSONString(map.getValue()));
                String tableName = map.getKey();
                String tableComment = objects.getString("tableComment");
                String entityName = GenTool.initcap(subStrByPrefix(map.getKey(), prefix));
                String priType = "";
                if (isGenEntity) {
                    priType = EntityGen.parse(tableName, tableComment, entityName, objects.getJSONArray("columnInfos").toJavaList(ColumnInfo.class));
                }
                if (isGenDao) {
                    DaoGen.parse(tableComment, entityName);
                }
                if (isGenService) {
                    ServiceGen.parse(tableComment, entityName);
                }
                if (isGenWeb) {
                    SwaggerWebGen.parse(tableComment, entityName, priType);
                }
            }

            System.out.println();

            /*Map<String, List> columnMap = new HashMap<>();
            List<ColumnInfo> columnInfos = null;
            while (resultSet.next()) {
                if (columnMap.containsKey(resultSet.getString(1))) {
                    columnInfos = columnMap.get(resultSet.getString(1));
                    columnInfos.add(new ColumnInfo(resultSet.getString(2), resultSet.getString(3), resultSet.getString(4), resultSet.getString(5), resultSet.getString(6)));
                } else {
                    columnInfos = new ArrayList<>();
                    columnInfos.add(new ColumnInfo(resultSet.getString(2), resultSet.getString(3), resultSet.getString(4), resultSet.getString(5), resultSet.getString(6)));
                    columnMap.put(resultSet.getString(1), columnInfos);
                }
            }

            for (Map.Entry<String, List> map : columnMap.entrySet()) {
                String tableName = subStrByPrefix(map.getKey(), prefix);
                if (isGenEntity) {
                    EntityGen.parse(tableName, map.getValue());
                }
                if (isGenDao) {
                    DaoGen.parse(tableName);
                }
                if (isGenService) {
                    ServiceGen.parse(tableName);
                }
                if (isGenWeb) {
                    SwaggerWebGen.parse(tableName);
                }
            }
            */

        } catch (SQLException e) {
            e.printStackTrace();
        } finally {
            try {
                con.close();
            } catch (SQLException e) {
                e.printStackTrace();
            }
        }
        System.out.println("生成完毕！");
    }

    /**
     * 功能：将输入字符串的首字母改成大写
     *
     * @param str
     * @return
     */
    public static String initcap(String str) {
        String[] arr = str.split("_");
        String result = "";
        if (arr.length == 1) {
            return initcap0(str);
        }
        for (int i = 0; i < arr.length; i++) {
            if (i == 0) {
                char[] ch = initcap0(arr[i].toLowerCase()).toCharArray();
                if (ch[0] >= 'a' && ch[0] <= 'z') {
                    ch[0] = (char) (ch[0] - 32);
                }
                result += new String(ch);
            } else {
                result += initcap0(arr[i].toLowerCase());
            }
        }
        return result;
    }

    /**
     * 功能：将输入字符串的首字母改成小写
     *
     * @param str
     * @return
     */
    public static String initcap2(String str) {
        String[] arr = str.split("_");
        String result = "";
        if (arr.length == 1) {
            return initcap1(str);
        }
        for (int i = 0; i < arr.length; i++) {
            if (i == 0) {
                char[] ch = initcap0(arr[i].toLowerCase()).toCharArray();
                if (ch[0] >= 'A' && ch[0] <= 'Z') {
                    ch[0] = (char) (ch[0] + 32);
                }
                result += new String(ch);
            } else {
                result += initcap0(arr[i].toLowerCase());
            }
        }
        return result;
    }

    private static String initcap1(String str) {
        char[] ch = str.toCharArray();
        if (ch[0] >= 'A' && ch[0] <= 'Z') {
            ch[0] = (char) (ch[0] + 32);
        }
        return new String(ch);
    }

    private static String initcap0(String str) {
        char[] ch = str.toCharArray();
        if (ch[0] >= 'a' && ch[0] <= 'z') {
            ch[0] = (char) (ch[0] - 32);
        }
        return new String(ch);
    }

    private static String subStrByPrefix(String str, String preFix) {
        return str.indexOf(preFix) == 0 ? str.substring(preFix.length()) : str;
    }
}
